/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package misc;

import geometry.Obstacle;
import geometry.Vertex;
import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileWriter;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.PrintWriter;
import java.util.Random;
import java.util.logging.Level;
import java.util.logging.Logger;

/**
 *
 * @author Michał 
 */
public class ProblemProfile {
    Vertex source,target;
    Obstacle obstacles[] = new Obstacle[0];
    Obstacle hulls[] = new Obstacle[0];
    double lengths[], limitations[][];
    int numOfAngles;
    int numOfObstacles;
    int iterToChange = -1;
    String filename;
    String nextFileName = "";
    
    public int getIterToChange() {
        return iterToChange;
    }

    public String getNextFileName() {
        return nextFileName;
    }
    
    public void setSource(Vertex s) {
        source = s;
    }
    
    public Vertex getSource() {
        return source;
    }
    
    public void setTarget(Vertex t) {
        target = t;
    }
    
    public Vertex getTarget() {
        return target;
    }
    
    public Obstacle[] getObstacles() {
     
        return obstacles;
    }
    
    public double[] getLengths() {
        return lengths;
    }
    
    public void generateNext(String fileToSave, int howMany) {
        ProblemProfile temp = new ProblemProfile();
        temp.loadFromFile(filename);
        for(int i=0; i!=howMany; i++) {
            temp.deviate();
            temp.setNext(fileToSave+(i+1)+".txt");
            temp.saveToFile("data\\"+fileToSave+i+".txt");
            System.out.println(fileToSave+i+".txt");
        }
    }
    
    public void deviate() {
        Random r = new Random();
        
        if(r.nextDouble()<0.5)
            target = new Vertex(target.getX() + r.nextDouble() - 0.5, target.getY() + r.nextDouble() -0.5);
       
        if(r.nextDouble()<0.3)
            obstacles[ r.nextInt( obstacles.length ) ].moveBy( r.nextDouble()-0.5, r.nextDouble()-0.5); 
        
        if(r.nextDouble()<0.3)  
            obstacles[ r.nextInt( obstacles.length ) ].rotate( r.nextDouble() );
    }
    
    public void saveToFile(String filename) {
        FileWriter outFile = null;
        try {
            outFile = new FileWriter(filename);
        } catch (IOException ex) {
            Logger.getLogger(ProblemProfile.class.getName()).log(Level.SEVERE, null, ex);
        }
        PrintWriter out = new PrintWriter(outFile);
        
        out.println("change 1");
        out.println("source " + source.getX() + " " + source.getY());
        out.println("target " + target.getX() + " " + target.getY());    
        out.println("next " + nextFileName);
        out.println("angles " + lengths.length);
        for(int i=0; i!=lengths.length; i++) {
            out.println(lengths[i] + " " + limitations[i][0] + " " + limitations[i][1]);
        }
        out.println("obstacles " + obstacles.length);
        for(int i=0; i!=obstacles.length; i++) 
        {
            out.println("new_obstacle " + obstacles[i].size());
            for(int j=0; j!=obstacles[i].size(); j++)
                out.println(obstacles[i].getEdgeAt(j).getBegin().getX() + " " + 
                        obstacles[i].getEdgeAt(j).getBegin().getY());
        }
        out.close();
    }
    
    public void loadFromFile(String filename) {
        String line;
        this.filename = filename;
        try {
            File inFile = new File(filename);
            BufferedReader br = new BufferedReader(new InputStreamReader(
                new FileInputStream(inFile)));

            String op;
            int angleCount=0;
            int obstacleCount=0;
            int obstacleSize = 0;
            int currentObstacleVertex = 0;
            Vertex currentObstacle[] = null;
            boolean angleMode = false;
            boolean obstacleMode = false;
            while((line=br.readLine())!=null) {
                op = line.split(" ")[0];
                if(angleMode) {
                    lengths[angleCount] = Double.parseDouble(line.split(" ")[0]);
                    limitations[angleCount][0] = Double.parseDouble(line.split(" ")[1]);
                    limitations[angleCount][1] = Double.parseDouble(line.split(" ")[2]);
                    angleCount++;
                    if(angleCount==numOfAngles) angleMode=false;
                } 
                else if(obstacleMode) { // obstacle size > 0
                    
                    currentObstacle[currentObstacleVertex] = new Vertex(
                            Double.parseDouble(line.split(" ")[0]),
                            Double.parseDouble(line.split(" ")[1]));
                    currentObstacleVertex++;
                    if(currentObstacleVertex>=obstacleSize) {
                        obstacleMode = false;
                        obstacles[obstacleCount] = new Obstacle(currentObstacle);
                        
                        //System.out.println("oc " + obstacleCount + " os " + obstacleSize);
                        obstacleCount++;
                    }
                }
                else if(op.equals("change")) {
                   iterToChange = Integer.parseInt(line.split(" ")[1]);
                }
                else if (op.equals("next")) {
                    nextFileName = line.split(" ")[1];
                }
                else if(op.equals("source")) {
                    double x = Double.parseDouble(line.split(" ")[1]);
                    double y = Double.parseDouble(line.split(" ")[2]);
                    setSource(new Vertex(x,y));
                }
                else if(op.equals("target")) {
                    double x = Double.parseDouble(line.split(" ")[1]);
                    double y = Double.parseDouble(line.split(" ")[2]);
                    setTarget(new Vertex(x,y));
                } 
                else if(op.equals("angles")) {
                    numOfAngles = Integer.parseInt(line.split(" ")[1]);
                    lengths = new double[numOfAngles];
                    limitations = new double[numOfAngles][2];
                    angleMode = true;
                }
                else if(op.equals("obstacles")) {
                    numOfObstacles = Integer.parseInt(line.split(" ")[1]);
                    obstacles = new Obstacle[numOfObstacles];
                }
                else if(op.equals("new_obstacle")) {
                    obstacleSize = Integer.parseInt(line.split(" ")[1]);
                    obstacleMode = true;
                    currentObstacle = new Vertex[obstacleSize];
                    currentObstacleVertex=0;
                }
            }
      
            br.close();
        } catch (FileNotFoundException ex) {
            System.out.println(ex.getMessage());
        } catch (IOException ex) {
            System.out.println(ex.getMessage());
        }
    }

    public double[][] getLimitations() {
        return limitations;
    }

    private void setNext(String string) {
        nextFileName = string;
    }
}
